package com.linshidream.intrachat.simplenio;

import java.io.IOException;
import java.net.InetSocketAddress;
import java.nio.ByteBuffer;
import java.nio.channels.SelectionKey;
import java.nio.channels.Selector;
import java.nio.channels.ServerSocketChannel;
import java.nio.channels.SocketChannel;
import java.nio.charset.StandardCharsets;
import java.util.Iterator;

/**
 * Created on 2025/7/24 18:25
 *
 * @author linshidream
 * @version 1.0.0
 * @description
 */

public class NioSimpleServer {

    public static void main(String[] args) throws IOException {


        // 1 创建 ServerSocketChannel 通道
        ServerSocketChannel channel = ServerSocketChannel.open();
        channel.bind(new InetSocketAddress(10000));
        channel.configureBlocking(false);

        //2、 创建一个 Selector 选择器
        Selector selector = Selector.open();
        channel.register(selector, SelectionKey.OP_ACCEPT);

        System.out.println("NIO 单线程服务端启动完成...");

        // 3、主循环监听事件开始轮询
        while (true) {
            // 阻塞直到有事件
            selector.select();

            Iterator<SelectionKey> iterator = selector.selectedKeys().iterator();
            while (iterator.hasNext()) {
                SelectionKey key = iterator.next();
                // 用完记得删除事件
                iterator.remove();

                if (key.isAcceptable()) {
                    ServerSocketChannel sc = (ServerSocketChannel) key.channel();
                    SocketChannel client = sc.accept();
                    client.configureBlocking(false);
                    System.out.println("客户端连接成功: " + client.getRemoteAddress());

                    // 建立连接后 再订阅读事件
                    client.register(selector, SelectionKey.OP_READ);
                }

                if (key.isReadable()) {
                    SocketChannel client = (SocketChannel) key.channel();
                    ByteBuffer buffer = ByteBuffer.allocate(1024);
                    int len = client.read(buffer);
                    if (len == -1) {
                        client.close();
                        continue;
                    }
                    buffer.flip();
                    String request = new String(buffer.array(), 0, len, StandardCharsets.UTF_8).trim();
                    System.out.println("服务端收到消息: " + request);

                    String response = "echo：" + request + "\n";
                    ByteBuffer wrap = ByteBuffer.wrap(response.getBytes(StandardCharsets.UTF_8));
                    client.write(wrap);
                    System.out.println("服务端发送消息: " + response);
                }
            }
        }
    }
}
